package com.usian.comment.service.impl;

import com.usian.comment.feign.UserFeign;
import com.usian.comment.service.CommentService;
import com.usian.model.base.BaseResult;
import com.usian.model.comment.*;
import com.usian.model.common.dtos.ResponseResult;
import com.usian.model.user.pojos.ApUser;
import com.usian.utils.threadlocal.ThreadLocalUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

@Service
public class CommentServiceImpl implements BaseResult, CommentService {
    @Autowired
    private MongoTemplate mongoTemplate;
    @Autowired
    private UserFeign userFeign;

    @Override
    public ResponseResult saveComment(CommentSaveDto dto) {
        if (dto == null || dto.articleId == null || StringUtils.isBlank(dto.content) || dto.chnnelId == null || dto.content.length() > 140)
            return paramError;
        Integer userId = ThreadLocalUtils.getUserId();
        if (userId == null) return needLogin;
        ApComment comment = new ApComment();
        comment.setAuthorId(userId);
        ApUser user = userFeign.getUserById(userId);
        comment.setAuthorName(user.getName());
        comment.setEntryId(dto.articleId);
        comment.setChannelId(dto.chnnelId);
        comment.setType((short) 0);
        comment.setContent(dto.content);
        comment.setImage(user.getImage());
        comment.setLikes(0);
        comment.setReply(0);
        comment.setCreatedTime(new Date());
        mongoTemplate.save(comment);
        return success;
    }

    @Override
    public ResponseResult like(CommentLikeDto dto) {
        if (dto == null || dto.getCommentId() == null || dto.getOperation() == null || (dto.getOperation() != 0 && dto.getOperation() != 1))
            return paramError;
        Integer userId = ThreadLocalUtils.getUserId();
        if (userId == null) return needLogin;
        //保存点赞数据
        if (dto.getOperation() == 0){
            ApCommentLike like = new ApCommentLike();
            like.setAuthorId(userId);
            like.setCommentId(dto.getCommentId());
            like.setOperation(dto.getOperation());
            mongoTemplate.save(like);
        } else {
            mongoTemplate.remove(Query.query(Criteria.where("authorId").is(userId).and("commentId").is(dto.getCommentId())),ApCommentLike.class);
        }
        //新增点赞数量
        ApComment comment = mongoTemplate.findById(dto.getCommentId(), ApComment.class);
        comment.setLikes(dto.getOperation() == 0 ?comment.getLikes()+1 : comment.getLikes() > 0 ? comment.getLikes() -1 : 0);
        mongoTemplate.save(comment);
        return success;
    }

    @Override
    public ResponseResult findByArticleId(CommentDto dto) {
        if (dto == null || dto.getArticleId() == null)return paramError;
        List<ApComment> commentList = mongoTemplate.find(Query.query(Criteria.where("entryId").is(dto.getArticleId()).and("createdTime").lt(dto.getMinDate())).limit(5).with(Sort.by(Sort.Direction.DESC, "createdTime")), ApComment.class);
        Integer userId = ThreadLocalUtils.getUserId();
        if (userId == null)return success(commentList);
        //在commentList中找到当前userId点赞的评论数据做标记
        List<String> commentIds = commentList.stream().map(m -> m.getId()).collect(Collectors.toList());
        //在以上评论列表中当前用户点赞的数据
        List<ApCommentLike> likeList = mongoTemplate.find(Query.query(Criteria.where("authorId").is(userId).and("commentId").in(commentIds)), ApCommentLike.class);

        List<ApCommentVo> vos = new ArrayList<>();
        for (ApComment comment : commentList) {
            ApCommentVo vo = new ApCommentVo();
            BeanUtils.copyProperties(comment,vo);
            for (ApCommentLike like : likeList) {
                if (comment.getId().equals(like.getCommentId()))vo.setOperation((short) 0);
            }
            vos.add(vo);
        }
        return success(vos);
    }
}
